﻿namespace Microsoft.SmallBasic.Library
{
    using Microsoft.SmallBasic.Library.Internal;
    using System;
    using System.Text;

    [SmallBasicType]
    public static class TextWindow
    {
        private static bool _windowVisible;

        public static void Clear()
        {
            VerifyAccess();
            Console.Clear();
        }

        public static void Hide()
        {
            if (_windowVisible && NativeHelper.FreeConsole())
            {
                _windowVisible = false;
            }
        }

        public static void Pause()
        {
            VerifyAccess();
            Console.WriteLine("Press any key to continue...");
            Console.ReadKey(true);
        }

        public static void PauseIfVisible()
        {
            if (_windowVisible)
            {
                Pause();
            }
        }

        public static void PauseWithoutMessage()
        {
            VerifyAccess();
            Console.ReadKey(true);
        }

        public static Primitive Read()
        {
            VerifyAccess();
            return new Primitive(Console.ReadLine());
        }

        [HideFromIntellisense]
        public static Primitive ReadKey()
        {
            VerifyAccess();
            return new string(Console.ReadKey(true).KeyChar, 1);
        }

        public static Primitive ReadNumber()
        {
            ConsoleKeyInfo info;
            VerifyAccess();
            StringBuilder builder = new StringBuilder();
            bool flag = false;
            int startIndex = 0;
        BEGIN:
            info = Console.ReadKey(true);
            char keyChar = info.KeyChar;
            bool flag2 = false;
            if ((keyChar == '-') && (startIndex == 0))
            {
                flag2 = true;
            }
            else if ((keyChar == '.') && !flag)
            {
                flag = true;
                flag2 = true;
            }
            else if ((keyChar >= '0') && (keyChar <= '9'))
            {
                flag2 = true;
            }
            if (flag2)
            {
                Console.Write(keyChar);
                builder.Append(keyChar);
                startIndex++;
                goto BEGIN;
            }
            if ((startIndex > 0) && (info.Key == ConsoleKey.Backspace))
            {
                Console.CursorLeft--;
                Console.Write(" ");
                Console.CursorLeft--;
                startIndex--;
                keyChar = builder[startIndex];
                if (keyChar == '.')
                {
                    flag = false;
                }
                builder.Remove(startIndex, 1);
                goto BEGIN;
            }
            if (info.Key != ConsoleKey.Enter)
            {
                goto BEGIN;
            }
            Console.WriteLine();
            if (builder.Length == 0)
            {
                return new Primitive(0);
            }
            return new Primitive(builder.ToString());
        }

        public static void Show()
        {
            if (!_windowVisible && NativeHelper.AllocConsole())
            {
                _windowVisible = true;
            }
        }

        private static void VerifyAccess()
        {
            if (!_windowVisible)
            {
                Show();
            }
        }

        public static void Write(Primitive data)
        {
            VerifyAccess();
            Console.Write((string) data);
        }

        public static void WriteLine(Primitive data)
        {
            VerifyAccess();
            Console.WriteLine((string) data);
        }

        public static Primitive BackgroundColor
        {
            get
            {
                VerifyAccess();
                return Console.BackgroundColor.ToString();
            }
            set
            {
                VerifyAccess();
                try
                {
                    Console.BackgroundColor = (ConsoleColor) Enum.Parse(typeof(ConsoleColor), (string) value, true);
                }
                catch
                {
                }
            }
        }

        public static Primitive CursorLeft
        {
            get
            {
                VerifyAccess();
                return new Primitive(Console.CursorLeft);
            }
            set
            {
                VerifyAccess();
                Console.CursorLeft = (int) value;
            }
        }

        public static Primitive CursorTop
        {
            get
            {
                VerifyAccess();
                return new Primitive(Console.CursorTop);
            }
            set
            {
                VerifyAccess();
                Console.CursorTop = (int) value;
            }
        }

        public static Primitive ForegroundColor
        {
            get
            {
                VerifyAccess();
                return Console.ForegroundColor.ToString();
            }
            set
            {
                VerifyAccess();
                try
                {
                    Console.ForegroundColor = (ConsoleColor) Enum.Parse(typeof(ConsoleColor), (string) value, true);
                }
                catch
                {
                }
            }
        }

        public static Primitive Left
        {
            get
            {
                RECT rect;
                VerifyAccess();
                NativeHelper.GetWindowRect(NativeHelper.GetConsoleWindow(), out rect);
                return rect.Left;
            }
            set
            {
                RECT rect;
                VerifyAccess();
                IntPtr consoleWindow = NativeHelper.GetConsoleWindow();
                NativeHelper.GetWindowRect(consoleWindow, out rect);
                NativeHelper.SetWindowPos(consoleWindow, IntPtr.Zero, (int) value, rect.Top, 0, 0, 1);
            }
        }

        public static Primitive Title
        {
            get
            {
                VerifyAccess();
                return new Primitive(Console.Title);
            }
            set
            {
                VerifyAccess();
                Console.Title = (string) value;
            }
        }

        public static Primitive Top
        {
            get
            {
                RECT rect;
                VerifyAccess();
                NativeHelper.GetWindowRect(NativeHelper.GetConsoleWindow(), out rect);
                return rect.Top;
            }
            set
            {
                RECT rect;
                VerifyAccess();
                IntPtr consoleWindow = NativeHelper.GetConsoleWindow();
                NativeHelper.GetWindowRect(consoleWindow, out rect);
                NativeHelper.SetWindowPos(consoleWindow, IntPtr.Zero, rect.Left, (int) value, 0, 0, 1);
            }
        }
    }
}

